//
// Created by wujehy on 2020/9/23.
//

#ifndef FLUTTERSDK_BASEDARTAPI_H
#define FLUTTERSDK_BASEDARTAPI_H
#include <stdio.h>
#include <stdbool.h>
#include <cstdint>
#include "Base.h"
#include "string"
// dart_api.h
typedef int64_t Dart_Port;

typedef enum {
    Dart_TypedData_kByteData = 0,
    Dart_TypedData_kInt8,
    Dart_TypedData_kUint8,
    Dart_TypedData_kUint8Clamped,
    Dart_TypedData_kInt16,
    Dart_TypedData_kUint16,
    Dart_TypedData_kInt32,
    Dart_TypedData_kUint32,
    Dart_TypedData_kInt64,
    Dart_TypedData_kUint64,
    Dart_TypedData_kFloat32,
    Dart_TypedData_kFloat64,
    Dart_TypedData_kFloat32x4,
    Dart_TypedData_kInvalid
} Dart_TypedData_Type;

typedef struct _Dart_WeakPersistentHandle* Dart_WeakPersistentHandle;

typedef void (*Dart_WeakPersistentHandleFinalizer)(
        void* isolate_callback_data,
        Dart_WeakPersistentHandle handle,
        void* peer);

// dart_native_api.h
typedef enum {
    Dart_CObject_kNull = 0,
    Dart_CObject_kBool,
    Dart_CObject_kInt32,
    Dart_CObject_kInt64,
    Dart_CObject_kDouble,
    Dart_CObject_kString,
    Dart_CObject_kArray,
    Dart_CObject_kTypedData,
    Dart_CObject_kExternalTypedData,
    Dart_CObject_kSendPort,
    Dart_CObject_kCapability,
    Dart_CObject_kUnsupported,
    Dart_CObject_kNumberOfTypes
} Dart_CObject_Type;

typedef struct _Dart_CObject {
    Dart_CObject_Type type;
    union {
        bool as_bool;
        int32_t as_int32;
        int64_t as_int64;
        double as_double;
        char* as_string;
        struct {
            Dart_Port id;
            Dart_Port origin_id;
        } as_send_port;
        struct {
            int64_t id;
        } as_capability;
        struct {
            intptr_t length;
            struct _Dart_CObject** values;
        } as_array;
        struct {
            Dart_TypedData_Type type;
            intptr_t length;
            uint8_t* values;
        } as_typed_data;
        struct {
            Dart_TypedData_Type type;
            intptr_t length;
            uint8_t* data;
            void* peer;
            Dart_WeakPersistentHandleFinalizer callback;
        } as_external_typed_data;
    } value;
} Dart_CObject;

typedef bool (*Dart_PostCObjectType)(Dart_Port port_id, Dart_CObject* message);

//#define LISTERTYPEKEYWORD "/listertype"

// 监听器返回的类型判断关键字
//const char* LISTER_TYPE_KEYWORD = "/listertype";
#define LISTER_TYPE_KEYWORD  "/listertype"
enum DartAppListernerTypeEnum{
    DartAppListernerType_MessageEvent = 1 ,
    DartAppListernerType_FriendEvent = 2 ,
    DartAppListernerType_TeamChangeEvent = 3 ,
    DartAppListernerType_OrderChangeEvent = 4 ,
    DartAppListernerType_Auth403ErrorEvent = 5 ,
    DartAppListernerType_OSSProcEvent = 6 ,
    DartAppListernerType_CreateNecessaryDirectionEvent = 7 ,
    DartAppListernerType_SDKInitBeforeEvent = 8 ,
    DartAppListernerType_SDKInitAfterEvent = 9 ,
    DartAppListernerType_SDKUnInitBeforeEvent = 10 ,
    DartAppListernerType_SDKUnInitAfterEvent = 11 ,
    DartAppListernerType_NetworkStatusChangeEvent = 12 ,
    DartAppListernerType_CurrentUserAppPathChangeEvent = 13 ,
    DartAppListernerType_SdkNotInitCallbackEvent = 14 ,
    DartAppListernerType_OssCurrentStatusChangeEvent = 15 ,
    DartAppListernerType_OssLocalChangeStatusEvent = 16 ,
};

//#ifdef __cplusplus
//extern "C" {
//#endif
    //　启动的时候注册
APICORE void RegisterDart_PostCObject(Dart_PostCObjectType _dartPostCObject);
APICORE void RegisterListernerDartPort(Dart_Port callbackPort);
//　回调函数的回调
extern "C" bool callDartCallBack(Dart_Port callbackPort ,  Dart_CObject *dart_object);

/**
 * @brief　对上面　的函数进行封装　只回传一个json
 */
extern "C" void callDartCallBackJson(Dart_Port callbackPort , const char* json);
extern "C" void callDartCallBackJsonNoLog(Dart_Port callbackPort , const char* json);
/**
 * @brief 对上层的函数封装
 * @param[in] code  错误码
 * @param[in] msg 错误信息
 * @param[in] json 返回的结构 bytes
 */
extern "C" void callDartCallbackData(Dart_Port callbackPort , int code , const std::string &msg, const std::string &json="");

/**
 * @brief 获取监听器的port
 */
extern "C" Dart_Port getListernerPort();
//void callbackToDartInt32(Dart_Port callbackPort, int32_t value);
//void callbackToDartStrArray(Dart_Port callbackPort, int length, char** values);
//#ifdef __cplusplus
//}
//#endif
#endif //FLUTTERSDK_BASEDARTAPI_H
